package com.yzk.train.business.controller;

import com.alibaba.csp.sentinel.annotation.SentinelResource;
import com.alibaba.csp.sentinel.slots.block.BlockException;
import com.yzk.train.business.request.ConfirmOrderDoReq;
import com.yzk.train.business.service.BeforeConfirmOrderService;
import com.yzk.train.business.service.ConfirmOrderService;
import com.yzk.train.business.utils.MathGenerator;
import com.yzk.train.common.exception.ExceptionEnum;
import com.yzk.train.common.response.Result;
import jakarta.annotation.Resource;
import jakarta.validation.Valid;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.util.ObjectUtils;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/confirm-order")
public class ConfirmOrderController {

    private static final Logger LOG = LoggerFactory.getLogger(ConfirmOrderController.class);

    @Resource
    private BeforeConfirmOrderService beforeConfirmOrderService;

    @Resource
    private ConfirmOrderService confirmOrderService;

    @Resource
    private StringRedisTemplate stringRedisTemplate;

    @Value("${spring.profiles.active}")
    private String env;

    @PostMapping("/do")
    @SentinelResource(value = "doConfirmApi", blockHandler = "doConfirmBlock")
    public Result<String> doConfirm(@Valid @RequestBody ConfirmOrderDoReq req) {
        if (!env.equals("dev")) {
            // 验证码校验
            String captchaToken = req.getCaptchaToken();
            String inputCode = req.getCaptchaCode();
            String codeForRedis = stringRedisTemplate.opsForValue().get(captchaToken);
            if (ObjectUtils.isEmpty(codeForRedis)) {
                return Result.fail("验证码已过期");
            } else if (!(new MathGenerator().verify(codeForRedis, inputCode))) {
                return Result.fail("验证码错误");
            } else {
                stringRedisTemplate.delete(captchaToken);
            }
        }
        Long id = beforeConfirmOrderService.beforeDoConfirm(req);
        return Result.ok(String.valueOf(id));
    }


    @GetMapping("/query-line-count/{id}")
    public Result<Integer> queryLineCount(@PathVariable Long id) {
        Integer count = confirmOrderService.queryLineCount(id);
        return Result.ok(count);
    }

    @GetMapping("/cancel-line/{id}")
    public Result<Integer> cancel(@PathVariable Long id) {
        Integer count = confirmOrderService.cancel(id);
        return Result.ok(count);
    }

    // 降级方法，需包含限流方法的所有参数和BlockException参数，且返回值要保持一致
    public Result<Object> doConfirmBlock(ConfirmOrderDoReq req, BlockException e) {
        LOG.info("ConfirmOrderController购票请求被限流");
        return Result.fail(ExceptionEnum.CONFIRM_ORDER_FLOW_EXCEPTION.getDesc());
    }

}
